package com.example.project.utils;

/**
 * Redmine 风格的时间格式化工具类 将存储的小时数值转换为用户友好的显示格式
 */
public class TimeFormatter {

	/**
	 * 将小时数转换为用户友好的显示格式
	 * 
	 * @param hours 小时数
	 * @return 格式化后的时间字符串
	 */
	public static String formatHours(Double hours) {
		if (hours == null) {
			return "";
		}

		// 处理整数小时
		if (hours == Math.floor(hours)) {
			return String.format("%.0fh", hours.intValue());
		}

		// 处理半小时的情况
		if (Math.abs(hours - Math.floor(hours) - 0.5) < 0.001) {
			int wholeHours = (int) Math.floor(hours);
			if (wholeHours == 0) {
				return "30m";
			} else {
				return String.format("%dh30m", wholeHours);
			}
		}

		// 处理分钟不为0或30的情况
		double minutes = hours * 60;
		int wholeMinutes = (int) Math.round(minutes);

		// 如果少于1小时且不是30分钟，直接显示分钟
		if (hours < 1 && wholeMinutes != 30) {
			return String.format("%dm", wholeMinutes);
		}

		int displayHours = wholeMinutes / 60;
		int displayMinutes = wholeMinutes % 60;

		// 如果分钟数为0，只显示小时
		if (displayMinutes == 0) {
			return String.format("%dh", displayHours);
		}

		// 如果小时数为0，只显示分钟
		if (displayHours == 0) {
			return String.format("%dm", displayMinutes);
		}

		// 否则显示小时和分钟
		return String.format("%dh%dm", displayHours, displayMinutes);
	}

	/**
	 * 将小时数转换为HH:MM格式
	 * 
	 * @param hours 小时数
	 * @return HH:MM格式的时间字符串
	 */
	public static String formatHoursToTime(Double hours) {
		if (hours == null) {
			return "";
		}

		int totalMinutes = (int) Math.round(hours * 60);
		int displayHours = totalMinutes / 60;
		int displayMinutes = totalMinutes % 60;

		return String.format("%d:%02d", displayHours, displayMinutes);
	}

	/**
	 * 将小时数转换为简化的显示格式 优先使用小数格式，除非有特殊需求
	 * 
	 * @param hours 小时数
	 * @return 简化的时间字符串
	 */
	public static String formatHoursSimple(Double hours) {
		if (hours == null) {
			return "";
		}

		// 如果是整数，去掉小数部分
		if (hours == Math.floor(hours)) {
			return String.format("%.0f", hours);
		}

		// 如果是小数，保留1-2位小数
		if (hours * 10 == Math.floor(hours * 10)) {
			return String.format("%.1f", hours);
		} else {
			return String.format("%.2f", hours);
		}
	}

	/**
	 * 根据用户偏好选择最佳显示格式
	 * 
	 * @param hours       小时数
	 * @param formatStyle 格式风格：decimal, time, mixed
	 * @return 格式化后的时间字符串
	 */
	public static String formatHoursWithStyle(Double hours, FormatStyle formatStyle) {
		if (hours == null) {
			return "";
		}

		switch (formatStyle) {
		case DECIMAL:
			return formatHoursSimple(hours) + "h";
		case TIME:
			return formatHoursToTime(hours);
		case MIXED:
		default:
			return formatHours(hours);
		}
	}

	/**
	 * 格式化时间范围
	 * 
	 * @param startHours  开始时间（小时）
	 * @param endHours    结束时间（小时）
	 * @param formatStyle 格式风格
	 * @return 格式化的时间范围字符串
	 */
	public static String formatTimeRange(Double startHours, Double endHours, FormatStyle formatStyle) {
		String start = formatHoursWithStyle(startHours, formatStyle);
		String end = formatHoursWithStyle(endHours, formatStyle);

		if (start.isEmpty() && end.isEmpty()) {
			return "";
		} else if (start.isEmpty()) {
			return "≤ " + end;
		} else if (end.isEmpty()) {
			return "≥ " + start;
		} else {
			return start + " - " + end;
		}
	}

	/**
	 * 格式化格式风格枚举
	 */
	public enum FormatStyle {
		DECIMAL, // 小数格式：2.5h
		TIME, // 时间格式：2:30
		MIXED // 混合格式：2h30m
	}

	/**
	 * 生成时间统计报告
	 * 
	 * @param estimatedHours 预期时间
	 * @param spentHours     实际耗时
	 * @param remainingHours 剩余时间
	 * @param formatStyle    格式风格
	 * @return 统计报告字符串
	 */
	public static String generateTimeReport(Double estimatedHours, Double spentHours, Double remainingHours,
			FormatStyle formatStyle) {
		StringBuilder report = new StringBuilder();
		report.append("时间统计报告\\n");
		report.append("============\\n");

		if (estimatedHours != null) {
			report.append(String.format("预期时间: %s\\n", formatHoursWithStyle(estimatedHours, formatStyle)));
		}

		if (spentHours != null) {
			report.append(String.format("实际耗时: %s\\n", formatHoursWithStyle(spentHours, formatStyle)));
		}

		if (remainingHours != null) {
			report.append(String.format("剩余时间: %s\\n", formatHoursWithStyle(remainingHours, formatStyle)));
		}

		// 计算效率
		if (estimatedHours != null && spentHours != null && estimatedHours > 0) {
			double efficiency = (estimatedHours - spentHours) / estimatedHours * 100;
			String efficiencyStr;
			if (efficiency > 0) {
				efficiencyStr = String.format("节约时间: %.1f%%", Math.abs(efficiency));
			} else {
				efficiencyStr = String.format("超时: %.1f%%", Math.abs(efficiency));
			}
			report.append(efficiencyStr + "\\n");
		}

		return report.toString();
	}

	// 测试方法
	public static void main(String[] args) {
		Double[] testCases = { null, 0.0, 0.25, 0.5, 0.75, 1.0, 1.25, 1.5, 1.75, 2.0, 2.33, 3.67, 4.5, 8.0, 12.5,
				24.0 };

		System.out.println("时间格式化测试:");
		System.out.println("小时数\\t\\t混合格式\\t时间格式\\t小数格式");
		System.out.println("------\\t\\t--------\\t--------\\t--------");

		for (Double hours : testCases) {
			String mixed = formatHours(hours);
			String time = formatHoursToTime(hours);
			String decimal = formatHoursSimple(hours);
			System.out.printf("%s\\t\\t%s\\t\\t%s\\t\\t%s\\n", hours != null ? String.format("%.2f", hours) : "null",
					mixed, time, decimal);
		}

		System.out.println("\\n时间范围格式化:");
		System.out.println(formatTimeRange(2.5, 5.75, FormatStyle.MIXED));
		System.out.println(formatTimeRange(null, 3.0, FormatStyle.DECIMAL));
		System.out.println(formatTimeRange(1.5, null, FormatStyle.TIME));

		System.out.println("\\n时间统计报告示例:");
		System.out.println(generateTimeReport(40.0, 32.5, 7.5, FormatStyle.MIXED));
	}
}